import logging
import time
from typing import List

from fastapi import APIRouter, Depends, Query, Path
from pydantic import Field, BaseModel
from sqlalchemy import text
from sqlalchemy.exc import SQLAlchemyError
from sqlalchemy.orm import Session

from commons.BaseResponse import BaseResponse
from commons.PaginationBase import PaginationBase
from datebase import get_db
from utils.EncryptionUtil import oauth2_scheme, EncryptionMiddleware

role_router = APIRouter(prefix="/sys/role", tags=["用户角色"])


class RoleGetModel(PaginationBase):
    sort: str = Field(default=None, description="排序字段")
    order: str = Field(default="desc", description="正序或者倒叙")
    role_name: str = Field(default=None, description="角色名")

# todo 8.角色资料
@role_router.get("/list", summary="角色查询")
def get_role_list(roleGetModel: RoleGetModel = Query(), db: Session = Depends(get_db)):
    sql = "select count(1) from am_sys_role where 1=1  "
    if roleGetModel.role_name is not None:
        sql = sql + " and name like :role_name "
    count_sql = sql
    # 数据总条数
    data_count = db.execute(text(count_sql), {"role_name": roleGetModel.role_name}).scalar()

    # 根据条件取出数据
    sql = "select id,name,description,user_count,to_char(create_time,'yyyy-mm-dd hh24:mi:ss') create_time,"
    sql = sql + "status,sort_seq,create_id,to_char(update_time,'yyyy-mm-dd hh24:mi:ss') update_time,update_id "
    sql = sql + " from am_sys_role where 1=1  "
    if roleGetModel.role_name is not None:
        sql = sql + " and name like :role_name "
    if roleGetModel.sort is not None:
        sql = sql + " order by  :sort  :order "
    sql = sql + " limit :limit offset :offset"
    total_sql = sql

    # 查询出的数据
    data = db.execute(text(total_sql),
                      {"role_name": roleGetModel.role_name,
                       "sort": roleGetModel.sort,
                       "order": roleGetModel.order,
                       "limit": roleGetModel.limit,
                       "offset": roleGetModel.offset
                       }).fetchall()
    if data is None or len(data) == 0:
        return BaseResponse.success("数据为空")
    data_list = []
    for key in range(len(data)):
        d1 = {}
        d1['id'] = data[key][0]
        d1['name'] = data[key][1]
        d1['description'] = data[key][2]
        d1['usercount'] = data[key][3]
        d1['createtime'] = data[key][4]
        d1['status'] = data[key][5]
        d1['sortSeq'] = data[key][6]
        d1['createId'] = data[key][7]
        d1['updateTime'] = data[key][8]
        d1['updateId'] = data[key][9]
        data_list.append(d1)
    info_dict = {"list": data_list, "limit": roleGetModel.limit, "page": roleGetModel.pageIndex,
                 "pages": (data_count + roleGetModel.pageSize - 1) // roleGetModel.pageSize,
                 "total": data_count}
    return BaseResponse.success(data=info_dict)


@role_router.get("/options", summary="获取全部角色信息")
def get_options(db: Session = Depends(get_db)):
    sql = "select id,name"
    sql = sql + " from am_sys_role"
    sql = sql + " order by id"

    userdata = db.execute(text(sql)).fetchall()
    mydata = []
    for key in range(len(userdata)):
        d1 = {}
        d1['value'] = userdata[key][0]
        d1['label'] = userdata[key][1]
        mydata.append(d1)

    data = {"list": mydata}
    return BaseResponse.success(data=data)


@role_router.get("/fsiteNoBelongOptions", summary="所属地区")
def get_fsite_options(db: Session = Depends(get_db)):
    sql = "select fsite_no,fsite_name from a_ts_site where 1=1 order by fsite_level"
    userdata = db.execute(text(sql)).fetchall()

    mydata = []
    for key in range(len(userdata)):
        d1 = {}
        d1['value'] = userdata[key][0]
        d1['label'] = userdata[key][1]
        mydata.append(d1)

    data = {"list": mydata}
    return BaseResponse.success(data=data)


class RoleCreate(BaseModel):
    id: int = Field(default=None, description="角色id，修改时填入")
    name: str = Field(description="角色名")
    description: str = Field(default="", description="角色描述")


@role_router.post("/create", summary="创建角色")
def do_create(roleCreate: RoleCreate, db: Session = Depends(get_db), token: str = Depends(oauth2_scheme)):
    try:
        with db.begin():
            # 获取用户id
            user = EncryptionMiddleware.decrypt_token(token)
            user_id = user['user_id']

            # 判断用户名是否已存在
            sql = "select id from am_sys_role where name= :role_name "
            data = db.execute(text(sql), {"role_name": roleCreate.name}).fetchall()
            if data is not None and len(data) > 0:
                return BaseResponse.error(message="角色已存在")

            # 获取id
            sql = "select nextval('am_sys_role_id_seq') as last_value"
            res = db.execute(text(sql)).fetchall()
            role_id = res[0][0]

            sql = "insert into am_sys_role(name,description,user_count,status,sort_seq,create_id,create_time,update_time,update_id)"
            sql = sql + " values( :name,:description,0,1,0,:user_id ,now(),now(), :user_id);"
            i = db.execute(text(sql), {"user_id": user_id,
                                       "name": roleCreate.name,
                                       "description": roleCreate.description})
            if i is None:
                return BaseResponse.error(message="新增角色失败")
            else:
                # 返回
                current_datetime = time.strftime('%Y-%m-%d %H:%M:%S', time.localtime())
                d1 = {}
                d1['id'] = role_id
                d1['name'] = roleCreate.name
                d1['description'] = roleCreate.description
                d1['usercount'] = 0
                d1['createTime'] = current_datetime
                d1['status'] = 1
                d1['sortseq'] = 1
                d1['createId'] = user_id
                d1['updateTime'] = current_datetime
                d1['updateId'] = user_id
                return BaseResponse.success(data=d1)
    except SQLAlchemyError as e:
        # 发生异常时自动回滚
        db.rollback()
        # 记录错误日志
        logging.error(f"数据库错误: {str(e)}")
        # 返回错误响应
        return BaseResponse.error(message="数据库操作失败")
    except Exception as e:
        db.rollback()
        logging.error(f"未知错误: {str(e)}")
        return BaseResponse.error(message="令牌过期")

@role_router.post("/update", summary="角色修改接口")
def update_role(roleCreate: RoleCreate, db: Session = Depends(get_db), token: str = Depends(oauth2_scheme)):
    user = EncryptionMiddleware.decrypt_token(token)
    user_id = user['user_id']

    sql = "select id from am_sys_role where name= :name and id<>:id"

    data = db.execute(text(sql), {"name": roleCreate.name, "id": roleCreate.id}).fetchall()
    if data is not None and len(data) > 0:
        return BaseResponse.error(message="角色名已存在")
    else:
        sql = "update am_sys_role"
        sql = sql + " set name= :name ,description= :description"
        sql = sql + " ,update_time=now(),update_id= :user_id"
        sql = sql + " where id=:id"
        i = db.execute(text(sql), {"id": user_id,
                                   "name": roleCreate.name,
                                   "description": roleCreate.description,
                                   "user_id": user_id})

        if i is None:
            return BaseResponse.error(message="失败")
        else:
            db.commit()
            return BaseResponse.success()


@role_router.post("/delete/{id}", summary="删除角色")
def delete_role(id: int = Path(description="角色id"), token: str = Depends(oauth2_scheme),
                db: Session = Depends(get_db)):
    try:
        user = EncryptionMiddleware.decrypt_token(token)
        user_id = user['user_id']
        # 查找是否正在被使用
        sql = "select count(1) from am_sys_user_role where role_id= :user_id"
        count = db.execute(text(sql), {"user_id": id}).scalar()
        if count > 0:
            return BaseResponse.error(message="删除失败，角色正在被使用")
        try:
            sql = "delete from am_sys_role where id= :id"
            db.execute(text(sql), {"id": id})

            sql = "delete from am_sys_role_permission where role_id= :id"
            db.execute(text(sql), {"id": id})
            db.commit()
            return BaseResponse.success()
        except Exception as e:
            db.rollback()
            return BaseResponse.error(message=str(e))
    except Exception as e:
        return BaseResponse.error(message="账号授权已过期")


class AssignCreate(BaseModel):
    roleId: int = Field(description="角色id")
    permIds: List[int] = Field(description="权限id列表")


@role_router.post("/assign", summary="保存角色权限")
def do_assign(assignCreate: AssignCreate, db: Session = Depends(get_db), token: str = Depends(oauth2_scheme)):
    try:
        sql = "delete from am_sys_role_permission where role_id= :role_id"
        db.execute(text(sql), {"role_id": assignCreate.roleId})
        for key in assignCreate.permIds:
            sql = "insert into am_sys_role_permission(role_id,permission_id)"
            sql = sql + " values(:role,:permission);"
            db.execute(text(sql), {"role": assignCreate.roleId, "permission": key})
        db.commit()
        return BaseResponse.success()
    except Exception as e:
        db.rollback()
        return BaseResponse.error(message=str(e))
